package com.edu.compile.compiler;

import com.edu.compile.AbstractCompileResult;
import com.edu.compile.AbstractCompilerParser;
import com.edu.compile.config.SwitchConfig;
import com.edu.compile.constant.SourceEnum;
import com.edu.compile.metadata.CaseMetadata;
import com.edu.compile.metadata.SourceMetadata;
import com.edu.compile.template.ftl.block.Switch;
import com.edu.compile.template.model.IfTrueConfig;
import com.edu.model.dto.NodeMetadata;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.List;

@Component("switch_compiler")
public class SwitchCompiler extends AbstractCompilerParser<SwitchConfig, Switch> {
    @Override
    public void compile(AbstractCompileResult abstractCompileResult, NodeMetadata nodeMetadata, SwitchConfig switchConfig, Switch aSwitch) {

        SourceMetadata sourceMetadata = switchConfig.getSourceMetadata();
        List<CaseMetadata> caseMetadataList = switchConfig.getCaseList();

        Object left = getValue(sourceMetadata, aSwitch);
        IfTrueConfig alwaysTrue = new IfTrueConfig();
        List<IfTrueConfig> elseIfList = new ArrayList<>();
        caseMetadataList.forEach(caseMetadata -> {
            Object right = getValue(caseMetadata.getSourceMetadata(), aSwitch);
            if (aSwitch.getAlwaysTrue() == null) {
                alwaysTrue.setComparator(caseMetadata.getComparator());
                alwaysTrue.setLeft(left);
                alwaysTrue.setRight(right);
                alwaysTrue.setAlwaysTrue(caseMetadata.isAlwaysTrue());
                aSwitch.setAlwaysTrue(alwaysTrue);
            } else {
                IfTrueConfig ifTrueConfig = new IfTrueConfig();
                ifTrueConfig.setComparator(caseMetadata.getComparator());
                ifTrueConfig.setLeft(left);
                ifTrueConfig.setRight(right);
                ifTrueConfig.setAlwaysTrue(caseMetadata.isAlwaysTrue());
                elseIfList.add(ifTrueConfig);
            }
        });
        aSwitch.setElseIfList(elseIfList);
    }

    private Object getValue(SourceMetadata config, Switch aSwitch) {
        if (SourceEnum.FIXED.test(config.getSource())) {
//            Object wrapper = ParamTypeEnum.convert(config.getType(), config.getValue());
//            return wrapper;
            return config.getValue();
        } else {
            aSwitch.addUndefinedCheck(config.getPort());
            aSwitch.addUndefinedCheck(config.getValue().toString());
            return config.getValue();
        }
    }
}
